package com.example.myapplication;

import android.app.PendingIntent;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.pm.PackageManager;
import android.graphics.drawable.ClipDrawable;
import android.graphics.drawable.Drawable;
import android.nfc.NfcAdapter;
import android.nfc.Tag;
import android.os.AsyncTask;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import android.view.View;
import android.view.WindowManager;
import android.widget.ImageButton;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;

import androidx.annotation.NonNull;
import androidx.annotation.StringRes;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.app.ActivityCompat;
import androidx.core.content.ContextCompat;
import androidx.core.view.GravityCompat;
import androidx.drawerlayout.widget.DrawerLayout;
import androidx.navigation.NavController;
import androidx.navigation.Navigation;
import androidx.navigation.ui.AppBarConfiguration;
import androidx.navigation.ui.NavigationUI;

import com.example.myapplication.databinding.ActivityMainBinding;
import com.example.myapplication.peripheral.UserBluetooth;
import com.google.android.material.navigation.NavigationView;
import com.st.st25android.AndroidReaderInterface;
import com.st.st25sdk.Helper;
import com.st.st25sdk.NFCTag;
import com.st.st25sdk.STException;
import com.st.st25sdk.type5.st25tvc.ST25TVCTag;

import java.util.ArrayList;
import java.util.List;

public class MainActivity extends AppCompatActivity {
    private static final String TAG = "MainActivity";
    private AppBarConfiguration mAppBarConfiguration;
    private ActivityMainBinding binding;

    private TextView tvRespondentName;
    private TextView tvRespondentDetails;
    private TextView tvRespondentBody;
    private static TextView tvBattery;
    private static ImageView BatteryIcon;
    private ImageButton btnEditRespondent;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        binding = ActivityMainBinding.inflate(getLayoutInflater());
        setContentView(binding.getRoot());

        setSupportActionBar(binding.appBarMain.toolbar);

        DrawerLayout drawer = binding.drawerLayout;
        NavigationView navigationView = binding.navView;

        // Passing each menu ID as a set of Ids because each
        // menu should be considered as top level destinations.
        mAppBarConfiguration = new AppBarConfiguration.Builder(
                R.id.nav_home, R.id.nav_gallery, R.id.nav_slideshow,R.id.nav_info)
                .setOpenableLayout(drawer)
                .build();
        NavController navController = Navigation.findNavController(this, R.id.nav_host_fragment_content_main);
        NavigationUI.setupActionBarWithNavController(this, navController, mAppBarConfiguration);
        NavigationUI.setupWithNavController(navigationView, navController);


        // 左侧栏实例
        View headerView = navigationView.getHeaderView(0);
        // 初始化视图
        tvRespondentName = headerView.findViewById(R.id.tv_respondent_name);
        tvRespondentDetails = headerView.findViewById(R.id.tv_respondent_details);
        tvRespondentBody = headerView.findViewById(R.id.tv_respondent_body);
        btnEditRespondent = headerView.findViewById(R.id.btn_edit_respondent);
        tvBattery = headerView.findViewById(R.id.battery_percent);
        // 设置编辑按钮点击事件
        btnEditRespondent.setOnClickListener(v -> {
            binding.drawerLayout.closeDrawer(GravityCompat.START);
            navController.navigate(R.id.nav_info);
        });
        // 启用硬件加速
        getWindow().setFlags(
                WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED,
                WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED
        );

        // 更新受访者信息
        updateRespondentInfo();
        // 开启权限
        checkAndRequestPermissions();
        // 开启蓝牙
        UserBluetooth.getInstance().init(MainActivity.this);
        // 初始化NFC
        initNfc();
    }
    static public void setBatteryPercent(int percent) {
        Message message = new Message();
        message.what = 1;
        message.arg1 = percent;
        handler.sendMessage(message);
    }

    static Handler handler = new Handler(new Handler.Callback() {
        @Override
        public boolean handleMessage(@NonNull Message msg) {
            switch (msg.what) {
                case 1: {
                    if (tvBattery != null) {
                        tvBattery.setText(msg.arg1+"%");
                    }
                }
                break;
            }
            return true;
        }
    });
    private static final int PERMISSION_REQUEST_CODE = 100;  // 可以是任意整数（通常用100, 101等）
    private void checkAndRequestPermissions() {
        List<String> permissionsNeeded = new ArrayList<>();

        // 蓝牙权限检查
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.BLUETOOTH_SCAN) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.BLUETOOTH_SCAN);
            }
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.BLUETOOTH_CONNECT) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.BLUETOOTH_CONNECT);
            }
        } else {
            // 旧版本蓝牙权限
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.BLUETOOTH) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.BLUETOOTH);
            }
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.BLUETOOTH_ADMIN) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.BLUETOOTH_ADMIN);
            }
            // 旧版本可能需要位置权限进行蓝牙扫描
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.ACCESS_FINE_LOCATION);
            }
        }

        // NFC权限 - 通常不需要运行时权限，只需在manifest中声明

        // 存储权限检查
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
            // Android 13+ 媒体权限
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.READ_MEDIA_IMAGES) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.READ_MEDIA_IMAGES);
            }
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.READ_MEDIA_VIDEO) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.READ_MEDIA_VIDEO);
            }
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.READ_MEDIA_AUDIO) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.READ_MEDIA_AUDIO);
            }
        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
            // Android 10-12 使用分区存储，可能不需要请求存储权限
            // 但如果需要访问旧式存储，可能需要请求
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.READ_EXTERNAL_STORAGE);
            }
        } else {
            // Android 9及以下
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.READ_EXTERNAL_STORAGE);
            }
            if (ContextCompat.checkSelfPermission(this,
                    android.Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
                permissionsNeeded.add(android.Manifest.permission.WRITE_EXTERNAL_STORAGE);
            }
        }

        // 请求所有需要的权限
        if (!permissionsNeeded.isEmpty()) {
            ActivityCompat.requestPermissions(this,
                    permissionsNeeded.toArray(new String[0]),
                    PERMISSION_REQUEST_CODE);
        }
    }
    @Override
    public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);

        if (requestCode == PERMISSION_REQUEST_CODE) {
            for (int i = 0; i < permissions.length; i++) {
                if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
                    // 权限被授予
                    System.out.println(permissions[i] + " 权限已授予");
                } else {
                    // 权限被拒绝
                    System.out.println(permissions[i] + " 权限被拒绝");
                    // 可以在这里向用户解释为什么需要这个权限
                }
            }
        }
    }

    @Override
    public boolean onSupportNavigateUp() {
        NavController navController = Navigation.findNavController(this, R.id.nav_host_fragment_content_main);
        return NavigationUI.navigateUp(navController, mAppBarConfiguration)
                || super.onSupportNavigateUp();
    }

    // 更新导航头部显示的受访者信息
    public void updateRespondentInfo() {
        SharedPreferences prefs = getSharedPreferences(getString(R.string.SharedPreferences), MODE_PRIVATE);

        String name = prefs.getString(getString(R.string.name), "");
        String gender = prefs.getString(getString(R.string.gender), "");
        int age = prefs.getInt(getString(R.string.age), 0);
        int height = prefs.getInt(getString(R.string.height), 0);
        int weight = prefs.getInt(getString(R.string.weight), 0);

        if (!name.isEmpty()) {
            tvRespondentName.setText(name);
            tvRespondentDetails.setText(String.format("性别: %s | 年龄: %d", gender, age));
            tvRespondentBody.setText(String.format("身高: %d cm | 体重: %d kg", height, weight));
        } else {
            tvRespondentName.setText("未设置受访者");
            tvRespondentDetails.setText("性别: - | 年龄: -");
            tvRespondentBody.setText("身高: - cm | 体重: - kg");
        }
    }

    /**
     * NFC初始化
     */
    public static short SMARTAG_END_ADDR_COMPACT_DATA   = 8192;
    public static short SMARTAG_BEGIN_ADDR_COMPACT_DATA = 120;
    public short LastSamplePointer = SMARTAG_BEGIN_ADDR_COMPACT_DATA;
    enum Action {
        LEAVE_UNTRACEABLE_MODE,
        INSTANTIATE_TAG,
        TOGGLE_UNTRACEABLE_MODE_PWD
    };
    enum ActionStatus {
        ACTION_SUCCESSFUL,
        ACTION_FAILED,
        TAG_NOT_IN_THE_FIELD,
        CONFIG_PASSWORD_NEEDED
    };
    private NfcAdapter mNfcAdapter;
    private PendingIntent mPendingIntent;
    private static NFCTag mTag;
    public static NFCTag getTag() {
        return mTag;
    }
    public void setTag(NFCTag nfcTag) {
        mTag = nfcTag;
    }
    @Override
    protected void onNewIntent(Intent intent) {
        super.onNewIntent(intent);
        setIntent(intent);
    }
    private void initNfc(){
        mNfcAdapter = NfcAdapter.getDefaultAdapter(this);
        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.S) {
            mPendingIntent = PendingIntent.getActivity(this, 0, new Intent(this, getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), PendingIntent.FLAG_MUTABLE);
        } else {
            mPendingIntent = PendingIntent.getActivity(this, 0, new Intent(this, getClass()).addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP), 0);
        }
    }

    @Override
    protected void onResume() {
        Intent intent = getIntent();
        Log.d(TAG, "Resume mainActivity intent: " + intent);
        super.onResume();

        if (mNfcAdapter != null) {
            Log.v(TAG, "enableForegroundDispatch");
            mNfcAdapter.enableForegroundDispatch(this, mPendingIntent, null /*nfcFiltersArray*/, null /*nfcTechLists*/);
        }
        Tag androidTag = intent.getParcelableExtra(NfcAdapter.EXTRA_TAG);
        if (androidTag != null) {
            // A tag has been taped
            byte[] uid = Helper.reverseByteArray(androidTag.getId());
            AndroidReaderInterface readerInterface = AndroidReaderInterface.newInstance(androidTag);
            new myAsyncTask(Action.LEAVE_UNTRACEABLE_MODE, readerInterface, uid).execute();
        }

        updateRespondentInfo();
    }
    private class myAsyncTask extends AsyncTask<Void, Void, ActionStatus> {
        Action mAction;
        byte[] mUid;
        AndroidReaderInterface mReaderInterface;
        public myAsyncTask(Action action, AndroidReaderInterface readerInterface, byte[] uid) {
            mAction = action;
            mUid = uid;
            mReaderInterface = readerInterface;
        }
        @Override
        protected ActionStatus doInBackground(Void... param) {
            ActionStatus result;

            try {
                switch(mAction) {
                    case LEAVE_UNTRACEABLE_MODE:
                        // The Instantiated Tag will support only a minimum set of commands
                        boolean sendInitCommands = false;
                        mTag = new ST25TVCTag(mReaderInterface, mUid, sendInitCommands);
                        result = ActionStatus.ACTION_SUCCESSFUL;
                        break;
                    case INSTANTIATE_TAG:
                        ST25TVCTag st25TVCTag = new ST25TVCTag(mReaderInterface, mUid);
                        st25TVCTag.setName("ST25TV02KC");
                        mTag = st25TVCTag;
                        result = ActionStatus.ACTION_SUCCESSFUL;
                        break;
                    default:
                        // Unknown action
                        result = ActionStatus.ACTION_FAILED;
                        break;
                }
            } catch (STException e) {
                switch (e.getError()) {
                    case CONFIG_PASSWORD_NEEDED:
                        result = ActionStatus.CONFIG_PASSWORD_NEEDED;
                        break;
                    case TAG_NOT_IN_THE_FIELD:
                        result = ActionStatus.TAG_NOT_IN_THE_FIELD;
                        break;
                    default:
                        e.printStackTrace();
                        result = ActionStatus.ACTION_FAILED;
                        break;
                }
            }
            return result;
        }
        @Override
        protected void onPostExecute(ActionStatus actionStatus) {
            switch(actionStatus) {
                case ACTION_SUCCESSFUL:
                    switch(mAction) {
                        case LEAVE_UNTRACEABLE_MODE:
                            //requestUntraceableModePwd();
                            break;
                        case INSTANTIATE_TAG:
                            // Display the menus related to this tag
                            //onTagDiscoveryCompleted(mTag, PRODUCT_ST_ST25TV02KC, null);
                            break;
                    }
                    break;
                case ACTION_FAILED:
                    //howToast(R.string.error_while_updating_the_tag);
                    break;

                case TAG_NOT_IN_THE_FIELD:
                    //showToast(R.string.tag_not_in_the_field);
                    break;
            }
            return;
        }
        private void showToast(@StringRes int id) {
            Toast.makeText(getApplication(), getResources().getString(id), Toast.LENGTH_LONG).show();
        }
    }
    @Override
    protected void onPause() {
        super.onPause();
        if (mNfcAdapter != null) {
            try {
                mNfcAdapter.disableForegroundDispatch(this);
                Log.v(TAG, "disableForegroundDispatch");
            } catch (IllegalStateException e) {
                Log.w(TAG, "Illegal State Exception disabling NFC. Assuming application is terminating.");
            }
            catch (UnsupportedOperationException e) {
                Log.w(TAG, "FEATURE_NFC is unavailable.");
            }
        }
    }
}